package com.example.sj10.util;

import android.content.ContentResolver;
import android.content.ContentValues;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.net.Uri;
import android.os.Build;
import android.os.Environment;
import android.provider.MediaStore;
import android.util.Log;

import androidx.core.content.FileProvider;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;

public class FileUtil {
    private static final String TAG = "FileUtil";
    private static final String AVATAR_DIR = "avatars";

    // 获取应用私有存储的头像目录
    public static File getAvatarDir(Context context) {
        File dir = new File(context.getExternalFilesDir(null), AVATAR_DIR);
        if (!dir.exists()) {
            dir.mkdirs();
        }
        return dir;
    }

    // 根据用户ID获取头像文件
    public static File getAvatarFile(Context context, String userId) {
        return new File(getAvatarDir(context), userId + ".jpg");
    }

    // 保存Bitmap到本地（用户ID作为文件名，确保用户隔离）
    public static boolean saveAvatar(Context context, String userId, Bitmap bitmap) {
        // 检查bitmap是否有效
        if (bitmap == null || bitmap.isRecycled()) {
            Log.e(TAG, "保存头像失败: bitmap无效");
            return false;
        }
        
        File file = getAvatarFile(context, userId);
        // 确保目录存在
        File dir = file.getParentFile();
        if (dir != null && !dir.exists()) {
            dir.mkdirs();
        }
        
        try (FileOutputStream fos = new FileOutputStream(file)) {
            // 压缩为JPG格式，支持PNG/WebP可调整格式
            bitmap.compress(Bitmap.CompressFormat.JPEG, 90, fos);
            fos.flush();
            return true;
        } catch (IOException e) {
            Log.e(TAG, "保存头像失败: " + e.getMessage());
            return false;
        }
    }

    /**
     * 从本地加载头像（根据用户ID）
     * 【核心需求1&4】头像展示与数据持久化
     * @param context 上下文
     * @param userId 用户ID
     * @return 如果存在自定义头像则返回Bitmap，否则返回null（由调用方处理默认头像）
     */
    public static Bitmap loadAvatar(Context context, String userId) {
        File file = getAvatarFile(context, userId);
        if (file.exists() && file.length() > 0) {
            try {
                Bitmap bitmap = BitmapFactory.decodeFile(file.getAbsolutePath());
                if (bitmap != null) {
                    Log.d(TAG, "成功加载用户头像: " + userId);
                    return bitmap;
                } else {
                    Log.w(TAG, "头像文件损坏，删除无效文件: " + file.getAbsolutePath());
                    file.delete(); // 删除损坏的文件
                }
            } catch (Exception e) {
                Log.e(TAG, "加载头像文件失败: " + e.getMessage());
            }
        } else {
            Log.d(TAG, "用户头像文件不存在，显示默认头像: " + userId);
        }
        // 返回null，由调用方使用默认头像
        return null;
    }

    /**
     * 从Uri获取Bitmap（适配Android 11，特别优化模拟器DCIM/Camera目录访问）
     */
    public static Bitmap getBitmapFromUri(Context context, Uri uri) {
        if (uri == null || context == null) {
            Log.e(TAG, "Uri或Context为空");
            return null;
        }

        Log.d(TAG, "开始从Uri加载图片: " + uri.toString());
        
        // 记录Uri的类型信息，便于调试
        String uriScheme = uri.getScheme();
        Log.d(TAG, "Uri方案: " + uriScheme + ", 权限: " + uri.getAuthority());
        
        // 尝试获取文件路径
        String filePath = getFilePathFromContentUri(context, uri);
        Log.d(TAG, "解析到的文件路径: " + filePath);
        
        // 【关键优化】对于模拟器环境，如果能直接获取到文件路径，优先尝试直接从文件加载
        // 这是处理Uri.fromFile()生成的URI的有效方法，特别是在Android 10+上
        if (filePath != null && filePath.contains("DCIM/Camera")) {
            Log.d(TAG, "检测到来自DCIM/Camera目录的图片路径，尝试直接从文件加载: " + filePath);
            Bitmap bitmap = decodeBitmapFromFile(filePath);
            if (bitmap != null) {
                Log.d(TAG, "成功直接从文件加载DCIM/Camera目录图片");
                return bitmap;
            }
        }
        
        // 特殊处理模拟器中可能的文件路径
        if (uriScheme != null && uriScheme.equals("content")) {
            try {
                // 尝试获取文件路径（对于某些ContentProvider可能有效）
                if (filePath != null && filePath.contains("DCIM/Camera")) {
                    Log.d(TAG, "检测到来自DCIM/Camera目录的图片: " + filePath);
                }
            } catch (Exception e) {
                Log.w(TAG, "获取文件路径失败: " + e.getMessage());
            }
        }

        InputStream inputStream = null;
        try {
            // 使用ContentResolver打开输入流
            inputStream = context.getContentResolver().openInputStream(uri);
            if (inputStream == null) {
                Log.e(TAG, "无法打开输入流，URI可能不可读");
                return null;
            }

            // 先获取图片尺寸，避免OOM
            BitmapFactory.Options options = new BitmapFactory.Options();
            options.inJustDecodeBounds = true;
            BitmapFactory.decodeStream(inputStream, null, options);
            
            // 记录图片信息
            Log.d(TAG, "图片原始尺寸: " + options.outWidth + "x" + options.outHeight + ", MIME类型: " + options.outMimeType);
            
            // 重置输入流
            inputStream.close();
            inputStream = context.getContentResolver().openInputStream(uri);

            // 计算合适的采样率
            int maxDimension = 1024; // 最大尺寸限制
            options.inSampleSize = calculateInSampleSize(options, maxDimension, maxDimension);
            Log.d(TAG, "计算的采样率: " + options.inSampleSize);
            
            options.inJustDecodeBounds = false;
            options.inPreferredConfig = Bitmap.Config.RGB_565; // 使用较低配置减少内存使用
            options.inDither = true;
            options.inScaled = true; // 支持缩放
            options.inPurgeable = true; // 允许系统在内存不足时回收
            options.inInputShareable = true;

            // 解码Bitmap
            Bitmap bitmap = BitmapFactory.decodeStream(inputStream, null, options);
            if (bitmap != null) {
                Log.d(TAG, "成功解码Bitmap，最终尺寸: " + bitmap.getWidth() + "x" + bitmap.getHeight());
            }
            return bitmap;
        } catch (FileNotFoundException e) {
            Log.e(TAG, "文件未找到: " + e.getMessage());
            Log.e(TAG, "请确认模拟器中已通过Device File Explorer将照片上传到sdcard/DCIM/Camera目录");
        } catch (IOException e) {
            Log.e(TAG, "IO异常: " + e.getMessage());
        } catch (OutOfMemoryError e) {
            Log.e(TAG, "内存不足: " + e.getMessage());
            // 内存不足时尝试更低的采样率
            try {
                if (inputStream != null) {
                    inputStream.close();
                }
                return decodeWithLowerMemory(context, uri);
            } catch (Exception ex) {
                Log.e(TAG, "低内存解码失败: " + ex.getMessage());
            }
        } catch (Exception e) {
            Log.e(TAG, "获取Bitmap异常: " + e.getMessage());
            e.printStackTrace();
        } finally {
            if (inputStream != null) {
                try {
                    inputStream.close();
                } catch (IOException e) {
                    Log.e(TAG, "关闭输入流异常: " + e.getMessage());
                }
            }
        }
        return null;
    }
    
    /**
     * 低内存模式解码，用于OOM时的后备方案
     */
    private static Bitmap decodeWithLowerMemory(Context context, Uri uri) { 
        Log.d(TAG, "尝试使用低内存模式解码图片");
        InputStream inputStream = null;
        try {
            inputStream = context.getContentResolver().openInputStream(uri);
            
            BitmapFactory.Options options = new BitmapFactory.Options();
            options.inJustDecodeBounds = true;
            BitmapFactory.decodeStream(inputStream, null, options);
            
            inputStream.close();
            inputStream = context.getContentResolver().openInputStream(uri);
            
            // 使用更低的采样率
            int maxDimension = 512; // 更低的最大尺寸
            options.inSampleSize = calculateInSampleSize(options, maxDimension, maxDimension);
            options.inJustDecodeBounds = false;
            options.inPreferredConfig = Bitmap.Config.RGB_565; // 更低的色彩配置
            options.inDither = true;
            options.inScaled = true;
            options.inPurgeable = true;
            options.inInputShareable = true;
            
            return BitmapFactory.decodeStream(inputStream, null, options);
        } catch (Exception e) {
            Log.e(TAG, "低内存解码失败: " + e.getMessage());
            return null;
        } finally {
            if (inputStream != null) {
                try {
                    inputStream.close();
                } catch (IOException e) {
                    Log.e(TAG, "关闭输入流异常: " + e.getMessage());
                }
            }
        }
    }
    
    /**
     * 尝试从Content Uri获取文件路径（辅助调试）
     */
    private static String getFilePathFromContentUri(Context context, Uri uri) {
        if (uri == null) return null;
        
        try {
            // 直接处理file://协议的Uri（适用于模拟器环境）
            if (uri.getScheme() != null && uri.getScheme().equals("file")) {
                return uri.getPath();
            }
            
            // 对于MediaStore的Uri尝试获取文件路径
            if (uri.getAuthority() != null && uri.getAuthority().contains("media")) {
                String[] projection = {MediaStore.Images.Media.DATA};
                try (android.database.Cursor cursor = context.getContentResolver().query(uri, projection, null, null, null)) {
                    if (cursor != null && cursor.moveToFirst()) {
                        int columnIndex = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
                        return cursor.getString(columnIndex);
                    }
                }
            }
        } catch (Exception e) {
            Log.w(TAG, "获取文件路径失败: " + e.getMessage());
        }
        return null;
    }
    
    /**
     * 针对模拟器环境的特殊方法：直接从文件路径加载Bitmap
     * 这是Uri.fromFile()在Android 10+上被限制后的备选方案
     */
    private static Bitmap decodeBitmapFromFile(String filePath) {
        if (filePath == null) return null;
        
        try {
            Log.d(TAG, "尝试直接从文件路径加载: " + filePath);
            File imageFile = new File(filePath);
            
            if (!imageFile.exists() || !imageFile.canRead()) {
                Log.e(TAG, "文件不存在或不可读: " + filePath);
                return null;
            }
            
            // 先获取图片尺寸，避免OOM
            BitmapFactory.Options options = new BitmapFactory.Options();
            options.inJustDecodeBounds = true;
            BitmapFactory.decodeFile(filePath, options);
            
            // 记录图片信息
            Log.d(TAG, "文件图片原始尺寸: " + options.outWidth + "x" + options.outHeight + ", MIME类型: " + options.outMimeType);
            
            // 计算合适的采样率
            int maxDimension = 1024; // 最大尺寸限制
            options.inSampleSize = calculateInSampleSize(options, maxDimension, maxDimension);
            Log.d(TAG, "计算的采样率: " + options.inSampleSize);
            
            // 设置优化选项
            options.inJustDecodeBounds = false;
            options.inPreferredConfig = Bitmap.Config.RGB_565; // 使用较低配置减少内存使用
            options.inDither = true;
            options.inScaled = true;
            options.inPurgeable = true;
            options.inInputShareable = true;
            
            // 直接从文件解码
            Bitmap bitmap = BitmapFactory.decodeFile(filePath, options);
            if (bitmap != null) {
                Log.d(TAG, "成功从文件解码Bitmap，最终尺寸: " + bitmap.getWidth() + "x" + bitmap.getHeight());
            }
            return bitmap;
        } catch (OutOfMemoryError e) {
            Log.e(TAG, "内存不足: " + e.getMessage());
            // 尝试低内存模式
            try {
                BitmapFactory.Options options = new BitmapFactory.Options();
                options.inSampleSize = 4; // 强制使用更高的采样率
                options.inPreferredConfig = Bitmap.Config.RGB_565;
                options.inScaled = true;
                return BitmapFactory.decodeFile(filePath, options);
            } catch (Exception ex) {
                Log.e(TAG, "低内存模式也失败: " + ex.getMessage());
            }
        } catch (Exception e) {
            Log.e(TAG, "从文件解码失败: " + e.getMessage());
        }
        return null;
    }

    /**
     * 计算Bitmap的采样率，避免OOM
     */
    private static int calculateInSampleSize(BitmapFactory.Options options, int reqWidth, int reqHeight) {
        final int height = options.outHeight;
        final int width = options.outWidth;
        int inSampleSize = 1;

        if (height > reqHeight || width > reqWidth) {
            final int halfHeight = height / 2;
            final int halfWidth = width / 2;

            // 计算最大的inSampleSize值，该值是2的幂，并且保证采样后的高度和宽度大于等于请求的高度和宽度
            while ((halfHeight / inSampleSize) >= reqHeight &&
                    (halfWidth / inSampleSize) >= reqWidth) {
                inSampleSize *= 2;
            }
        }

        return inSampleSize;
    }

    // 删除旧头像文件（隐私保护）
    public static boolean deleteOldAvatar(Context context, String userId) {
        File oldFile = getAvatarFile(context, userId);
        if (oldFile.exists()) {
            return oldFile.delete();
        }
        return true; // 文件不存在也认为删除成功
    }

    /**
     * 将Bitmap保存到系统相册（适配Android 11+）
     * @param context 上下文
     * @param bitmap 要保存的图片
     * @param displayName 显示名称（文件名）
     * @param mimeType MIME类型，如"image/jpeg"、"image/png"
     * @return 保存成功返回Uri，失败返回null
     */
    public static Uri saveImageToGallery(Context context, Bitmap bitmap, String displayName, String mimeType) {
        if (bitmap == null || bitmap.isRecycled()) {
            Log.e(TAG, "保存到相册失败: bitmap无效");
            return null;
        }

        ContentResolver resolver = context.getContentResolver();
        Uri imageUri = null;
        OutputStream outputStream = null;

        try {
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
                // Android 10+ 使用MediaStore API
                ContentValues values = new ContentValues();
                values.put(MediaStore.Images.Media.DISPLAY_NAME, displayName);
                values.put(MediaStore.Images.Media.MIME_TYPE, mimeType);
                values.put(MediaStore.Images.Media.RELATIVE_PATH, Environment.DIRECTORY_PICTURES + "/MyApp");
                values.put(MediaStore.Images.Media.IS_PENDING, 1); // 标记为待处理

                imageUri = resolver.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
                if (imageUri != null) {
                    outputStream = resolver.openOutputStream(imageUri);
                    if (outputStream != null) {
                        // 根据MIME类型选择压缩格式
                        Bitmap.CompressFormat format = "image/png".equals(mimeType) ? 
                            Bitmap.CompressFormat.PNG : Bitmap.CompressFormat.JPEG;
                        bitmap.compress(format, 90, outputStream);
                        
                        // 标记完成
                        values.clear();
                        values.put(MediaStore.Images.Media.IS_PENDING, 0);
                        resolver.update(imageUri, values, null, null);
                        
                        Log.d(TAG, "图片已保存到相册: " + imageUri);
                        return imageUri;
                    }
                }
            } else {
                // Android 9及以下使用传统方式
                String fileName = displayName;
                if (!fileName.contains(".")) {
                    fileName += mimeType.equals("image/png") ? ".png" : ".jpg";
                }
                
                File picturesDir = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES);
                File appDir = new File(picturesDir, "MyApp");
                if (!appDir.exists()) {
                    appDir.mkdirs();
                }
                
                File imageFile = new File(appDir, fileName);
                outputStream = new FileOutputStream(imageFile);
                
                Bitmap.CompressFormat format = "image/png".equals(mimeType) ? 
                    Bitmap.CompressFormat.PNG : Bitmap.CompressFormat.JPEG;
                bitmap.compress(format, 90, outputStream);
                
                // 通知媒体扫描器
                ContentValues values = new ContentValues();
                values.put(MediaStore.Images.Media.DATA, imageFile.getAbsolutePath());
                values.put(MediaStore.Images.Media.DISPLAY_NAME, displayName);
                values.put(MediaStore.Images.Media.MIME_TYPE, mimeType);
                
                imageUri = resolver.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
                Log.d(TAG, "图片已保存到相册: " + imageFile.getAbsolutePath());
                return imageUri;
            }
        } catch (IOException e) {
            Log.e(TAG, "保存图片到相册失败: " + e.getMessage());
            // 如果保存失败，删除可能创建的记录
            if (imageUri != null && Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
                resolver.delete(imageUri, null, null);
            }
        } finally {
            if (outputStream != null) {
                try {
                    outputStream.close();
                } catch (IOException e) {
                    Log.e(TAG, "关闭输出流失败: " + e.getMessage());
                }
            }
        }
        return null;
    }

    /**
     * 将本地文件保存到系统相册
     * @param context 上下文
     * @param sourceFile 源文件
     * @param displayName 显示名称
     * @return 保存成功返回true
     */
    public static boolean saveFileToGallery(Context context, File sourceFile, String displayName) {
        if (!sourceFile.exists()) {
            Log.e(TAG, "源文件不存在: " + sourceFile.getAbsolutePath());
            return false;
        }
        
        Bitmap bitmap = BitmapFactory.decodeFile(sourceFile.getAbsolutePath());
        if (bitmap == null) {
            Log.e(TAG, "无法解码图片文件: " + sourceFile.getAbsolutePath());
            return false;
        }
        
        // 根据文件扩展名确定MIME类型
        String fileName = sourceFile.getName().toLowerCase();
        String mimeType = "image/jpeg"; // 默认
        if (fileName.endsWith(".png")) {
            mimeType = "image/png";
        } else if (fileName.endsWith(".webp")) {
            mimeType = "image/webp";
        }
        
        Uri uri = saveImageToGallery(context, bitmap, displayName, mimeType);
        bitmap.recycle(); // 释放内存
        
        return uri != null;
    }
}